﻿using System;
using System.Collections.Generic;
using System.Configuration.Provider;
using System.Linq;
using System.Text;
using System.Web.Security;

namespace BOSS.Web
{
    /// <summary>
    /// 在内存中提供具体实现的角色提供器
    /// </summary>
    public class InMemoryRoleProvider : RoleProvider
    {
        /// <summary>
        /// IDictionary&lt;ROLE_NAME, HashSet&lt;USER_NAME&gt;&gt;
        /// </summary>
        private IDictionary<string, HashSet<string>> m_userRoles = new Dictionary<string, HashSet<string>>();
        private string m_applicationName;

        /// <summary>
        /// 获取 / 设置 应用程序名称
        /// </summary>
        public override string ApplicationName
        {
            get
            {
                return m_applicationName;
            }
            set
            {
                this.m_applicationName = value;
            }
        }

        /// <summary>
        /// 创建角色
        /// </summary>
        /// <param name="roleName"></param>
        public override void CreateRole(string roleName)
        {
            if (!this.m_userRoles.ContainsKey(roleName))
            {
                this.m_userRoles.Add(roleName, new HashSet<string>());
            }
        }

        /// <summary>
        /// 删除角色
        /// </summary>
        /// <param name="roleName"></param>
        /// <param name="throwOnPopulatedRole"></param>
        /// <returns></returns>
        public override bool DeleteRole(string roleName, bool throwOnPopulatedRole)
        {
            if (this.m_userRoles.ContainsKey(roleName))
            {
                if (throwOnPopulatedRole)
                {
                    if (this.m_userRoles[roleName].Count > 0)
                    {
                        throw new ProviderException("角色正在使用中！");
                    }
                }
                this.m_userRoles.Remove(roleName);
            }
            return true;
        }

        /// <summary>
        /// 判断角色是否存在
        /// </summary>
        /// <param name="roleName"></param>
        /// <returns></returns>
        public override bool RoleExists(string roleName)
        {
            return this.m_userRoles.ContainsKey(roleName);
        }

        /// <summary>
        /// 获取所有角色
        /// </summary>
        /// <returns></returns>
        public override string[] GetAllRoles()
        {
            List<string> roles = new List<string>();
            roles.AddRange(this.m_userRoles.Keys);
            return roles.ToArray();
        }

        /// <summary>
        /// 将用户添加到角色中
        /// </summary>
        /// <param name="usernames"></param>
        /// <param name="roleNames"></param>
        public override void AddUsersToRoles(string[] usernames, string[] roleNames)
        {
            foreach (string roleName in roleNames)
            {
                HashSet<string> users;
                if (this.m_userRoles.ContainsKey(roleName))
                {
                    users = this.m_userRoles[roleName];
                }
                else
                {
                    users = new HashSet<string>();
                    this.m_userRoles.Add(roleName, users);
                }

                foreach (string username in usernames)
                {
                    users.Add(username);
                }
            }
        }

        /// <summary>
        /// 查找拥有指定角色，且用户名满足匹配条件的用户
        /// </summary>
        /// <param name="roleName"></param>
        /// <param name="usernameToMatch"></param>
        /// <returns></returns>
        public override string[] FindUsersInRole(string roleName, string usernameToMatch)
        {
            if (!this.m_userRoles.ContainsKey(roleName))
            {
                return new string[] { };
            }

            List<string> users = new List<string>();
            foreach (string username in this.m_userRoles[roleName])
            {
                if (username.StartsWith(usernameToMatch))
                {
                    users.Add(username);
                }
            }
            return users.ToArray();
        }

        /// <summary>
        /// 查找指定用户的角色
        /// </summary>
        /// <param name="username"></param>
        /// <returns></returns>
        public override string[] GetRolesForUser(string username)
        {
            List<string> roles = new List<string>();
            foreach (string roleName in this.m_userRoles.Keys)
            {
                HashSet<string> users = this.m_userRoles[roleName];
                if (users.Contains(username))
                {
                    roles.Add(roleName);
                }
            }
            return roles.ToArray();
        }

        /// <summary>
        /// 查找指定角色的用户
        /// </summary>
        /// <param name="roleName"></param>
        /// <returns></returns>
        public override string[] GetUsersInRole(string roleName)
        {
            if (!this.m_userRoles.ContainsKey(roleName))
            {
                return new string[] { };
            }

            List<string> users = new List<string>();
            users.AddRange(this.m_userRoles[roleName]);
            return users.ToArray();
        }

        /// <summary>
        /// 检查指定用户是否用户特定的权限
        /// </summary>
        /// <param name="username"></param>
        /// <param name="roleName"></param>
        /// <returns></returns>
        public override bool IsUserInRole(string username, string roleName)
        {
            if (!this.m_userRoles.ContainsKey(roleName))
            {
                return false;
                //string prefix = roleName + ".";
                //foreach (string subRole in this.m_userRoles.Keys)
                //{
                //    if (subRole.StartsWith(prefix))
                //    {
                //        if (this.m_userRoles[subRole].Contains(username))
                //        {
                //            return true;
                //        }
                //    }
                //}
                //return false;
            }
            return this.m_userRoles[roleName].Contains(username);
        }

        /// <summary>
        /// 将指定用户从指定角色中移除
        /// </summary>
        /// <param name="usernames"></param>
        /// <param name="roleNames"></param>
        public override void RemoveUsersFromRoles(string[] usernames, string[] roleNames)
        {
            foreach (string roleName in roleNames)
            {
                if (this.m_userRoles.ContainsKey(roleName))
                {
                    HashSet<string> users = this.m_userRoles[roleName];
                    foreach (string username in usernames)
                    {
                        users.Remove(username);
                    }
                }
            }
        }
    }
}
